package com.ruoyi.serverinfo.controller;

import com.ruoyi.common.annotation.Anonymous;
import com.ruoyi.serverinfo.config.TshockFileConfig;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.FileSystemResource;
import org.springframework.core.io.Resource;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.HashMap;
import java.util.Map;

@RestController
@RequestMapping("/api/tshock/file")
@CrossOrigin(origins = "*", maxAge = 3600) // 更明确的跨域配置
public class TshockFileController {

    @Autowired
    private TshockFileConfig fileConfig;

    // 头像上传（保持匿名）
    @PostMapping("/upload/avatar")
    @Anonymous
    public ResponseEntity<Map<String, Object>> uploadAvatar(@RequestParam("file") MultipartFile file) {
        return uploadFile(file, "avatar");
    }

    // 横幅上传（保持匿名）
    @PostMapping("/upload/banner")
    @Anonymous
    public ResponseEntity<Map<String, Object>> uploadBanner(@RequestParam("file") MultipartFile file) {
        return uploadFile(file, "banner");
    }

    // 核心文件访问接口（重点修复）
    @GetMapping("/access/{folder}/{filename:.+}") // 更清晰的路径拆分：文件夹/文件名
    @Anonymous // 强制匿名访问
    public ResponseEntity<Resource> accessFile(
            @PathVariable String folder, // 文件夹（avatar或banner）
            @PathVariable String filename) { // 文件名（含后缀）
        try {
            // 构建完整文件路径（使用Path更安全）
            Path filePath = Paths.get(fileConfig.getUploadPath())
                    .resolve(folder)
                    .resolve(filename)
                    .normalize(); // 处理路径中的..等特殊字符

            // 验证文件是否存在且在允许的目录内（安全校验）
            if (!Files.exists(filePath) || !Files.isRegularFile(filePath) ||
                    !filePath.startsWith(Paths.get(fileConfig.getUploadPath()))) {
                return ResponseEntity.status(HttpStatus.NOT_FOUND).body(null);
            }

            // 读取文件资源
            Resource resource = new FileSystemResource(filePath);

            // 设置响应头（指定内容类型）
            String contentType = Files.probeContentType(filePath);
            HttpHeaders headers = new HttpHeaders();
            headers.add(HttpHeaders.CONTENT_TYPE, contentType);
            headers.add(HttpHeaders.CONTENT_DISPOSITION, "inline; filename=\"" + filename + "\"");

            return ResponseEntity.ok()
                    .headers(headers)
                    .body(resource);
        } catch (IOException e) {
            return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(null);
        }
    }

    // 通用上传逻辑（抽取复用）
    private ResponseEntity<Map<String, Object>> uploadFile(MultipartFile file, String folder) {
        Map<String, Object> result = new HashMap<>();
        try {
            if (file.isEmpty()) {
                result.put("success", false);
                result.put("message", "文件不能为空");
                return ResponseEntity.badRequest().body(result);
            }

            // 验证文件类型（示例：仅允许图片）
            String contentType = file.getContentType();
            if (contentType == null || !contentType.startsWith("image/")) {
                result.put("success", false);
                result.put("message", "仅支持图片文件");
                return ResponseEntity.badRequest().body(result);
            }

            // 构建存储路径
            Path uploadDir = Paths.get(fileConfig.getUploadPath()).resolve(folder);
            if (!Files.exists(uploadDir)) {
                Files.createDirectories(uploadDir); // 自动创建目录
            }

            // 生成唯一文件名（避免覆盖）
            String originalFilename = file.getOriginalFilename();
            String fileExt = originalFilename.substring(originalFilename.lastIndexOf("."));
            String filename = System.currentTimeMillis() + fileExt;

            // 保存文件
            Path destination = uploadDir.resolve(filename);
            file.transferTo(destination);

            // 返回访问URL（与访问接口路径对应）
            String fileUrl = "/api/tshock/file/access/" + folder + "/" + filename;
            result.put("success", true);
            result.put("url", fileUrl);
            result.put("message", "上传成功");
            return ResponseEntity.ok(result);

        } catch (Exception e) {
            result.put("success", false);
            result.put("message", "上传失败：" + e.getMessage());
            return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(result);
        }
    }
}
    